using System;
using System.Collections.Generic;
using System.Text;
using Jbe.TestSuite.TestDevices.Interface;
using Jbe.TestSuite.TestDevices.FunctionGenerator.ControlView.Presentation;
using Jbe.TestSuite.TestDevices.FunctionGenerator.Interface;
using Jbe.TestSuite.TestDevices.FunctionGenerator.ControlView.Properties;
using Microsoft.Practices.Composite.Regions;
using Jbe.TestSuite.Infrastructure.Interface;
using Jbe.Composite.Extensions;
using System.Collections.Specialized;
using Jbe.TestSuite.Infrastructure.Interface.Documents;
using Jbe.TestSuite.TestDevices.FunctionGenerator.ControlView.Applications;

namespace Jbe.TestSuite.TestDevices.FunctionGenerator.ControlView.Services
{
    internal class ViewController : IControlView
    {
        private readonly IApplicationContainer container;
        private readonly IRegionManager regionManager;
        private readonly IDevice device;
        private readonly IFunctionGenerator functionGenerator;
        private readonly DelegateCommand closeCommand;
        private string name;
        private FunctionGeneratorPresentationModel presentationModel;


        public ViewController(IApplicationContainer container, IRegionManager regionManager, IDevice device, IFunctionGenerator functionGenerator)
        {
            this.container = container;
            this.regionManager = regionManager;
            this.device = device;
            this.device.Disconnected += DeviceDisconnected;
            this.functionGenerator = functionGenerator;
            
            this.closeCommand = new DelegateCommand(CloseView, CanCloseView);
            DocumentCommands.Close.RegisterCommand(closeCommand);
        }


        public IDevice Device
        {
            get { return device; }
        }

        public string Name
        {
            get { return name; }
            set
            {
                name = value;
                if (presentationModel != null) { presentationModel.Name = value; }
            }
        }


        public void Show()
        {
            if (presentationModel == null)
            {
                IFunctionGeneratorView view = container.Resolve<IFunctionGeneratorView>();
                presentationModel = new FunctionGeneratorPresentationModel(view, functionGenerator);
                presentationModel.Name = Name;
                presentationModel.ConfigureClick += PresentationModelConfigureClick;

                presentationModel.View.DataContext = presentationModel;
                regionManager.Regions[ShellRegionNames.ContentRegion].ActiveViews.CollectionChanged += ActiveViewsCollectionChanged;
                regionManager.Regions[ShellRegionNames.ContentRegion].Add(presentationModel.View);
                
                closeCommand.RaiseCanExecuteChanged();
            }
            regionManager.Regions[ShellRegionNames.ContentRegion].Activate(presentationModel.View);
        }

        public void Close()
        {
            CloseView();

            device.Disconnected -= DeviceDisconnected;
            device.Disconnect();
        }

        private bool CanCloseView()
        {
            return presentationModel != null;
        }

        private void CloseView()
        {
            if (CanCloseView())
            {
                regionManager.Regions[ShellRegionNames.ContentRegion].Remove(presentationModel.View);
                regionManager.Regions[ShellRegionNames.ContentRegion].ActiveViews.CollectionChanged -= ActiveViewsCollectionChanged;

                presentationModel.ConfigureClick -= PresentationModelConfigureClick;
                presentationModel = null;
            }
            closeCommand.RaiseCanExecuteChanged();
        }

        private void ActiveViewsCollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
        {
            if (e.NewItems != null && e.NewItems.Contains(presentationModel.View)) { closeCommand.IsActive = true; }
            else if (e.OldItems != null && e.OldItems.Contains(presentationModel.View)) { closeCommand.IsActive = false; }
        }

        private void DeviceDisconnected(object sender, EventArgs e)
        {
            Close();
        }

        private void PresentationModelConfigureClick(object sender, EventArgs e)
        {
            IConfigurationEditView configView = container.Resolve<IConfigurationEditView>();
            IFunctionGeneratorConfig config = functionGenerator.Config.Clone();
            ConfigurationEditPresentationModel configPresentationModel = new ConfigurationEditPresentationModel(configView, config, Name);
            
            if (configPresentationModel.ShowDialog() == true)
            {
                functionGenerator.Config = configPresentationModel.Config;
            }
        }
    }
}
